1 /* 2 * The MIT License (MIT) 3 * 4 * Copyright (c) 2014 Devisualization (Richard Andrew Cattermole) 5 * 6 * Permission is hereby granted, free of charge, to any person obtaining a copy 7 * of this software and associated documentation files (the "Software"), to deal 8 * in the Software without restriction, including without limitation the rights 9 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 10 * copies of the Software, and to permit persons to whom the Software is 11 * furnished to do so, subject to the following conditions: 12 * 13 * The above copyright notice and this permission notice shall be included in all 14 * copies or substantial portions of the Software. 15 * 16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 19 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 21 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 22 * SOFTWARE. 23 */ 24 module devisualization.window.context.direct3d; 25 26 version(Have_directx_d) { 27 import devisualization.window.window; 28 import devisualization.window.interfaces.context; 29 30 class Direct3dContext : IContext { 31 import devisualization.image.image; 32 import winapi = windows; 33 import directx.d3d11; 34 35 private { 36 winapi.HWND hWnd; 37 Window window; 38 39 ID3D11Device dev; 40 ID3D11DeviceContext devcon; 41 IDXGISwapChain swapchain; 42 ID3D11RenderTargetView backbuffer; 43 } 44 45 this(Window window, WindowConfig config) { 46 this.window = window; 47 hWnd = window.hwnd; 48 49 init(); 50 } 51 52 @property { 53 void activate() {} 54 55 void destroy() { 56 swapchain.Release(); 57 backbuffer.Release(); 58 dev.Release(); 59 devcon.Release(); 60 } 61 62 void swapBuffers() { 63 swapchain.Present(0, 0); 64 } 65 66 WindowContextType type() { return WindowContextType.Direct3D; } 67 68 string toolkitVersion() { 69 import std.conv : text; 70 return text(devcon.GetType) ~ " " ~ text(dev.GetFeatureLevel()); 71 } 72 73 string shadingLanguageVersion() { 74 switch(dev.GetFeatureLevel()) { 75 case D3D_FEATURE_LEVEL_9_1: 76 case D3D_FEATURE_LEVEL_9_2: 77 return "2"; 78 case D3D_FEATURE_LEVEL_9_3: 79 return "2.0b"; 80 case D3D_FEATURE_LEVEL_10_0: 81 case D3D_FEATURE_LEVEL_10_1: 82 return "4"; 83 case D3D_FEATURE_LEVEL_11_0: 84 return "5"; 85 //case D3D_FEATURE_LEVEL_11_1: 86 // return "5 with logical blend operations"; 87 88 default: 89 return null; 90 } 91 } 92 93 ID3D11Device device() { return dev; } 94 ID3D11DeviceContext deviceContext() { return devcon; } 95 IDXGISwapChain swapChain() { return swapchain; } 96 ID3D11RenderTargetView backBuffer() { return backbuffer; } 97 } 98 99 private { 100 void init() { 101 import std.c..string : memset; 102 103 // create a struct to hold information about the swap chain 104 DXGI_SWAP_CHAIN_DESC scd; 105 106 // clear out the struct for use 107 memset(&scd, 0, DXGI_SWAP_CHAIN_DESC.sizeof ); 108 109 // fill the swap chain description struct 110 scd.BufferCount = 1; // one back buffer 111 scd.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM; // use 32-bit color 112 scd.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT; // how swap chain is to be used 113 scd.OutputWindow = hWnd; // the window to be used 114 scd.SampleDesc.Count = 4; // how many multisamples 115 scd.Windowed = true; // windowed/full-screen mode 116 117 // create a device, device context and swap chain using the information in the scd struct 118 D3D11CreateDeviceAndSwapChain(null, 119 D3D_DRIVER_TYPE_HARDWARE, 120 null, 121 0, 122 null, 123 0, 124 D3D11_SDK_VERSION, 125 &scd, 126 &swapchain, 127 &dev, 128 null, 129 &devcon); 130 131 // get the address of the back buffer 132 ID3D11Texture2D pBackBuffer; 133 swapchain.GetBuffer(0, &IID_ID3D11Texture2D, cast(void**)&pBackBuffer); 134 135 // use the back buffer address to create the render target 136 dev.CreateRenderTargetView(pBackBuffer, null, &backbuffer); 137 pBackBuffer.Release(); 138 139 // set the render target as the back buffer 140 devcon.OMSetRenderTargets(1, &backbuffer, null); 141 142 winapi.RECT winsize; 143 winapi.GetClientRect(hWnd, &winsize); 144 145 // Set the viewport 146 D3D11_VIEWPORT viewport; 147 memset(&viewport, 0, D3D11_VIEWPORT.sizeof); 148 149 viewport.TopLeftX = 0; 150 viewport.TopLeftY = 0; 151 viewport.Width = winsize.right; 152 viewport.Height = winsize.bottom; 153 154 devcon.RSSetViewports(1, &viewport); 155 } 156 } 157 } 158 }